regenerate or something
[clinton/website/site/unknownlamer.org.git] / Metaobject Protocols.html
index 05901c2..f629002 100644 (file)
@@ -7,7 +7,10 @@
     <meta name="generator" content="muse.el" />
     <meta http-equiv="Content-Type"
           content="text/html; charset=utf-8" />
-<link rel="stylesheet" href="default.css" media="screen" />
+    <link href="http://feeds.unknownlamer.org/rss/site-updates" 
+          rel="alternate" type="application/rss+xml" title="Updates Feed" />
+
+<link rel="stylesheet" href="default.css" />
   </head>
   <body>
     <h1>Metaobject Protocols</h1>
 <dd>
 <dl>
 <dt>
-<a href="#sec4">Classes for scratch data and types</a>
+<a href="#sec4">Classes for Scratch Data and Types</a>
 </dt>
 <dt>
-<a href="#sec5">Generics with methods that implement protocols</a>
+<a href="#sec5">Generics with Methods that Implement Protocols</a>
 </dt>
 </dl>
 </dd>
 <dd>
 <dl>
 <dt>
-<a href="#sec20">Top level <strong>must</strong> call lower level functions</a>
+<a href="#sec20">Top Level <strong>Must</strong> Call Lower Level Methods</a>
 </dt>
 <dt>
-<a href="#sec21">Lower level methods are easier to customize</a>
+<a href="#sec21">Lower Level Methods are Easier to Customize</a>
 </dt>
 </dl>
 </dd>
 <a href="#sec23">Memoization</a>
 </dt>
 <dt>
-<a href="#sec24">Cleaner Code</a>
+<a href="#sec24">Constant Shared Return Values</a>
 </dt>
 </dl>
 </dd>
 <dt>
-<a href="#sec25">Procedural Only Where Neccesary</a>
+<a href="#sec25">Procedural Only Where Necessary</a>
 </dt>
-</dl>
-</dd>
 <dt>
-<a href="#sec26">Examples</a>
+<a href="#sec26">Real World</a>
 </dt>
 <dd>
 <dl>
 <dt>
-<a href="#sec27">Object Inspector</a>
-</dt>
-<dt>
-<a href="#sec28">Observer Design Pattern</a>
+<a href="#sec27">UCW and Arnesi</a>
 </dt>
 <dt>
-<a href="#sec29">Real World</a>
+<a href="#sec28">CLSQL</a>
 </dt>
-<dd>
-<dl>
 <dt>
-<a href="#sec30">UCW and Arnesi</a>
-</dt>
-<dt>
-<a href="#sec31">CLSQL</a>
-</dt>
-<dt>
-<a href="#sec32">Elephant</a>
+<a href="#sec29">Elephant</a>
 </dt>
 </dl>
 </dd>
 </dl>
 </dd>
 <dt>
-<a href="#sec33">Sources &amp;amp; Further Reading</a>
+<a href="#sec30">Sources and Further Reading</a>
 </dt>
 <dd>
 <dl>
 <dt>
-<a href="#sec34">Sources</a>
+<a href="#sec31">Sources</a>
 </dt>
 <dd>
 <dl>
 <dt>
-<a href="#sec35">The Art of the Metaobject Protocol</a>
+<a href="#sec32">The Art of the Metaobject Protocol</a>
 </dt>
 <dt>
-<a href="#sec36">CLOS MOP Specification</a>
+<a href="#sec33">CLOS MOP Specification</a>
 </dt>
 <dt>
-<a href="#sec37">Metaobject Protocols: Why We Want Them and What Else They Can Do</a>
+<a href="#sec34">Metaobject Protocols: Why We Want Them and What Else They Can Do</a>
 </dt>
 <dt>
-<a href="#sec38">Why Are Black Boxes so Hard to Reuse?</a>
+<a href="#sec35">Why Are Black Boxes so Hard to Reuse?</a>
 </dt>
 </dl>
 </dd>
 <dt>
-<a href="#sec39">Further Reading</a>
+<a href="#sec36">Further Reading</a>
 </dt>
 <dd>
 <dl>
 <dt>
-<a href="#sec40">A Metaobject Protocol for C++</a>
+<a href="#sec37">A Metaobject Protocol for C++</a>
+</dt>
+<dt>
+<a href="#sec38">Open Implementations and Metaobject Protocols</a>
+</dt>
+</dl>
+</dd>
+<dt>
+<a href="#sec39">Software</a>
 </dt>
+<dd>
+<dl>
 <dt>
-<a href="#sec41">Open Implementations and Metaobject Protocols</a>
+<a href="#sec40">Closer to MOP</a>
 </dt>
 </dl>
 </dd>
@@ -226,9 +226,8 @@ significantly more powerful as it encourages complete encapsulation
 through its use of classes primarily for method specialization rather
 than for state storage.</p>
 
-
 <h4><a name="sec4" id="sec4"></a>
-Classes for scratch data and types</h4>
+Classes for Scratch Data and Types</h4>
 
 <p class="first">In CLOS classes store data in slots (which are the same as data
 members). Encapsulation is not provided; any bit of code can use
@@ -236,52 +235,53 @@ members). Encapsulation is not provided; any bit of code can use
 first, but encapsulation is of questionable importance as the slots
 are meant only to be used by the protocol defined around the class.</p>
 
-<p>Classes are defined with defclass</p>
+<p>Classes are defined with <code>defclass</code></p>
 
 <pre class="src">
-(<span style="color: #00ffff;">defclass</span> <span style="color: #98fb98;">name</span> (superclasses ...)
-  ((slot-name <span style="color: #b0c4de;">:accessor</span> slot-accessor ...)
+(<span class="emacs-face-keyword">defclass</span> <span class="emacs-face-type">name</span> (superclasses ...)
+  ((slot-name <span class="emacs-face-builtin">:accessor</span> slot-accessor ...)
    ...)
   (class-options ...))
 
-(<span style="color: #00ffff;">defclass</span> <span style="color: #98fb98;">example</span> ()
-  ((foo <span style="color: #b0c4de;">:accessor</span> foo-of <span style="color: #b0c4de;">:initform</span> 5)))
+(<span class="emacs-face-keyword">defclass</span> <span class="emacs-face-type">example</span> ()
+  ((foo <span class="emacs-face-builtin">:accessor</span> foo-of <span class="emacs-face-builtin">:initform</span> 5)))
 
-(<span style="color: #00ffff;">defclass</span> <span style="color: #98fb98;">example-child</span> (example)
-  ((bar <span style="color: #b0c4de;">:accessor</span> bar-of <span style="color: #b0c4de;">:initform</span> (list 1 2 3))))
+(<span class="emacs-face-keyword">defclass</span> <span class="emacs-face-type">example-child</span> (example)
+  ((bar <span class="emacs-face-builtin">:accessor</span> bar-of <span class="emacs-face-builtin">:initform</span> (list 1 2 3))))
 </pre>
 
-<p>Slot defintions have several option; the above example shows only the
+<p>Slot definitions have several options; the above example shows only the
 <code>:accessor</code> and <code>:initform</code> options which are the most commonly
 used. <code>:accessor</code> generates an accessor for the slot (e.g. if you have
-an instance of <code>example</code> you can <code>(setf (foo-of some-example-instance) 'some-value)</code> to set and <code>(foo-of some-example-instance)</code> to access the
+an instance of <code>example</code> you can <code>(setf (foo-of some-example-instance)
+'some-value)</code> to set and <code>(foo-of some-example-instance)</code> to access the
 value). <code>:initform</code> provides a default initial value for the slot as a
-symbolic expression to be evaluated when an instance is created.</p>
+symbolic expression to be evaluated when an instance is created in the
+lexical environment of the class definition.</p>
 
 
 <h4><a name="sec5" id="sec5"></a>
-Generics with methods that implement protocols</h4>
+Generics with Methods that Implement Protocols</h4>
 
 <p class="first">Generics are like normal functions in Lisp, but they only provide a
 lambda list (parameter list). Methods are added to the generic which
-specialize on the types of their parameters, and provide the actual
-implementation. This allows for rich layered protocols to be developed
-which can enable selective modification of individual facets with
-minimal code.</p>
+specialize on the types of their parameters and provide an
+implementation. This allows writing rich layered protocols which can
+enable selective modification of individual facets with minimal code.</p>
 
 <pre class="src">
-(<span style="color: #00ffff;">defgeneric</span> <span style="color: #87cefa;">generic</span> (parameters ...)
+(<span class="emacs-face-keyword">defgeneric</span> <span class="emacs-face-function-name">generic</span> (parameters ...)
   (options) ...)
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">generic-name</span> ((parameter type) parameter ...)
-  <span style="color: #b3b3b3;">"documentation string"</span>
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">generic-name</span> ((parameter type) parameter ...)
+  <span class="emacs-face-doc">"documentation string"</span>
   body)
 
-(<span style="color: #00ffff;">defgeneric</span> <span style="color: #87cefa;">foo</span> (bar baz quux)
-  (<span style="color: #b0c4de;">:documentation</span> <span style="color: #b3b3b3;">"Process the baz with the quux capacitor to make the
+(<span class="emacs-face-keyword">defgeneric</span> <span class="emacs-face-function-name">foo</span> (bar baz quux)
+  (<span class="emacs-face-builtin">:documentation</span> <span class="emacs-face-doc">"Process the baz with the quux capacitor to make the
 foo widget fly into the sky at warp speed"</span>))
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">foo</span> ((bar example) baz (quux capacitor))
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">foo</span> ((bar example) baz (quux capacitor))
   (launch bar (process-with quux baz)))
 </pre>
 
@@ -298,34 +298,34 @@ reasons outside of the scope of this presentation.</p>
 Limitations of Default Language Behavior</h2>
 
 <p class="first">The behavior of a language is a compromise between many competing
-issues that attempts to be as generally useful as possible, and most
-applications will have no issue with the default behavior. There are,
-however, certain applications that could be cleanly written with minor
-modifications to the behavior of the language, but would be impossible
-or quite difficult to write otherwise.</p>
+issues that attempts to be as generally useful as possible so that
+<em>most</em> applications will have no issue with the default behavior. There
+are, however, certain applications that could be cleanly written with
+minor modifications to the behavior of the language, but would be
+impossible or quite difficult to write otherwise.</p>
 
 <h3><a name="sec7" id="sec7"></a>
 Slot Storage</h3>
 
 <p class="first">Most languages choose to preallocate storage for all of the slots of
-an instance. Imagine a contact database that stored information about
-people as slots of the class. There may be dozens of slots, but often
-many of them will be left blank. If slot storage is preallocated much
-memory will be wasted and the system may not be able to fit into the
-memory of the hardware it must run on (perhaps for financial reasons,
-huge datasets, etc.).</p>
+an instance. Now imagine a contact database that stores information
+about people in slots of a class. There may be dozens of slots, but
+often many of them will be left blank. If slot storage is preallocated
+much memory will be wasted and the database may not be able to fit
+into the memory of the hardware it must run on (perhaps for financial
+reasons, huge datasets, etc.).</p>
 
 <p>To save memory the author of the contact database must implement his
 own system to store properties and allocate them lazily. This
 represents a fair bit of effort, and would implement a system that
-differed from the existing slot system of classes only in the method
-of data storage.</p>
+differed from the existing slot system of classes only regarding slot
+storage.</p>
 
-<p>It would be useful if there were a way to customize instance
-allocation. The customizations would be minor and require overriding
+<p>It would be useful if there were a way to customize slot allocation in
+instances. The customizations would be minor and require overriding
 only the initial allocation behavior and the behavior of the first
 assignment to the slot. It is a a trivial problem in a language that
-allows customization of these.</p>
+allows customization of these behaviors.</p>
 
 
 <h3><a name="sec8" id="sec8"></a>
@@ -334,7 +334,9 @@ Design Patterns</h3>
 <p class="first">Design Patterns are generalized versions of common patterns found in
 programs. Many of them are merely methods to get around deficiencies
 in the language, and can be quite messy to implement in some
-languages.</p>
+languages. Ideally a pattern would be subsumed by the language, but
+real world constraints require language standards to remain fairly
+static.</p>
 
 
 
@@ -342,7 +344,7 @@ languages.</p>
 Metasoftware</h2>
 
 <p class="first">Some types of programs could be written easily if the language were
-customizable, but are nearly impossible to write when it is not.</p>
+customizable but are nearly impossible to write when it is not.</p>
 
 <h3><a name="sec10" id="sec10"></a>
 Runtime Generated Classes</h3>
@@ -351,26 +353,25 @@ Runtime Generated Classes</h3>
 own objects, attach behaviors to the objects, and perhaps mix
 different objects together to create new ones. When you abstract the
 problem this looks just like an object system!  Wouldn't it be nice if
-your program could create new objects and methods on the fly portably?</p>
+your program could create new classes and methods on the fly portably?</p>
 
 
 <h3><a name="sec11" id="sec11"></a>
 Object Inspection</h3>
 
-<p class="first">Imagine if you were developing a complicated program with many
-different objects that interacted in fairly complex ways. A tool to
-inspect the structure of objects while debugging would be quite
-useful, but in a traditional language would be impossible to implement
-portably. This could force you to purchase a certain compiler
-implementation which provided one, and even then would more than
-likely not be customizable.</p>
+<p class="first">Imagine you were developing a complicated program with many different
+objects that interacted in fairly complex ways. A tool to inspect the
+structure of objects while debugging would be quite useful, but in a
+traditional language would be impossible to implement portably. This
+could force you to purchase a certain compiler implementation which
+provided an inspector, and even then would likely not be customizable.</p>
 
 <p>This problem can be generalized to apply to most debugging tools; it
 would be useful to write such tools portably because users of the
 <em>language</em> and not the <em>compiler</em> need to debug software. Sharing
 infrastructure would result in better tools (more developers), and
-save man-years of wasted effort that comes with having to rewrite
-non-portable functionality from scratch multiple times.</p>
+save the man-years of wasted effort that comes with having to rewrite
+unportable tools from scratch multiple times.</p>
 
 
 
@@ -380,17 +381,17 @@ Metaobject Protocols</h2>
 <h3><a name="sec13" id="sec13"></a>
 Limited/Generalized Internals of the Implementation</h3>
 
-<p class="first">A Metaobject protocol is a generalized and limited subset of the
-underlying implementation of the language. It is generalized and
-limited in scope to allow for multiple implementation strategies;
-this, along with careful design, is essential because programming
-language research is ever advancing and new techniques for creating
-more reliable and faster implementations are still being discovered.</p>
+<p class="first">A Metaobject Protocol (MOP) is a generalized and limited subset of the
+underlying language implementation. It is limited to allow multiple
+implementation strategies; this, along with careful design, is
+essential because programming language research is ever advancing and
+new techniques for creating more reliable and faster implementations
+are still being discovered.</p>
 
 <p>This subset of the implementation is exported as a set of methods on
-metaobjects. Thus the system is implemented in itself. The system can
-then be customized using the extension and overriding features of the
-system.</p>
+metaobjects. Thus the language is implemented in itself. The system
+can then be customized using the extension and overriding features of
+the language itself.</p>
 
 
 <h3><a name="sec14" id="sec14"></a>
@@ -399,250 +400,137 @@ Classes of MOPs</h3>
 <h4><a name="sec15" id="sec15"></a>
 Reflective</h4>
 
-<p class="first">A reflective MOP provides a functional/procedural interface to
-information about the system. It exposes class relationships, the
-methods are attached to a generic, etc. A reflective MOP often
-provides some functionality for creating new classes at runtime.</p>
+<p class="first">A reflective MOP provides an interface to information <em>about</em> the
+running system. It exposes class relationships, the methods attached
+to a generic, etc. A reflective MOP often provides some functionality
+for creating new classes at runtime. Smalltalk was one of the first
+languages to expose a reflective MOP.</p>
 
 <h5>Example: Object Inspector</h5>
 
-
-<h5>Example: Runtime Generated Classes and Methods</h5>
-
-
-
-<h4><a name="sec16" id="sec16"></a>
-Intercessory</h4>
-
-<p class="first">Intercessory MOPs allow the user to customize language behavior by
-implementing methods which override certain aspects of the language
-behavior. This class of MOPs are what make MOPs especially
-powerful. No longer must a problem be restructured to fit the
-implementation language; the underyling language can be reshaped to
-fit the task at hand, and obfuscation of the intended structure of the
-application can be avoided.</p>
-
-<h5>Example: Lazily Allocated Slots</h5>
-
-
-<h5>Example: Observer Design Pattern</h5>
-
-
-
-
-<h3><a name="sec17" id="sec17"></a>
-Violation of Encapsulation?</h3>
-
-<p class="first">A MOP may seem like a violation of encapsulation by revealing some
-implementation details, but in reality a well designed protocol does
-not reveal anything which was not already exposed. Implementation
-decisions affect users, and some of these details do leak through to
-higher levels (e.g. the memory layout of slots). Implicit in the
-protocol specification are these implementation details, and the MOP
-merely makes this limited subset available for customization.</p>
-
-<p>A MOP makes it possible to customize certain implementation decisions
-that do not <strong>radically</strong> alter the behavior of the base language. The
-conceptual vocabulary of the system retains its meaning, and so code
-written in one dialect can interact with code written in another
-without knowing that they speak different ones.</p>
-
-
-
-<h2><a name="sec18" id="sec18"></a>
-MOP Design Principles</h2>
-
-<h3><a name="sec19" id="sec19"></a>
-Layered Protocol</h3>
-
-<p class="first">A layered protocol design is good for both meta and normal object
-protocols, and enables a combinatorial explosion of customizations to
-the protocol.</p>
-
-<h4><a name="sec20" id="sec20"></a>
-Top level <strong>must</strong> call lower level functions</h4>
-
-<p class="first">The top level methods of a layered metaobject protocol are required to
-call certain methods to perform some tasks. This both makes it easier
-to customize the top level methods (which perform very broad tasks) by
-providing some pieces of them for the programmer, and allows more
-customization to be done by opening up the replacement of lower level
-functions as a way to alter a small detail of the high level behavior.</p>
-
-
-<h4><a name="sec21" id="sec21"></a>
-Lower level methods are easier to customize</h4>
-
-<p class="first">The lower level methods of a MOP are limited in scope and can be
-implemented easily. Often the changes to language behavior that are
-wanted are very small, and having methods that perform simple tasks
-which are often customized reduces the effort required to extend the
-system.</p>
-
-
-
-<h3><a name="sec22" id="sec22"></a>
-Functional Where Possible</h3>
-
-<p class="first">Functional protocols are preferred for MOPs (and object protocol in
-general). Functional protocols open up several optimizations for the
-implementation without burdening the user of the protocol.</p>
-
-<h4><a name="sec23" id="sec23"></a>
-Memoization</h4>
-
-<p class="first">Memoization is the process of saving the results of a function call
-for future use. This avoids expensive recomputation of values which
-have not changed (recall that a true function will always return the
-same result when given the same arguments).</p>
-
-<p>A functional MOP can be optimized easily by exploiting this property
-to memoize the return values of calls to expensive operations. A MOP
-must be be very fast to avoid making programs unusably slow, and
-memoization is able to give an appreciable speedup in many cases
-without an insignificant burden on memory usage.</p>
-
-<h5>Constant Shared Return Values</h5>
-
-<p>Disallowing the modification of values returned by protocol methods
-allows the implementation to return large data structures by reference
-to avoid expensive copying without having to do expensive data
-integrity checks.</p>
-
-
-
-<h4><a name="sec24" id="sec24"></a>
-Cleaner Code</h4>
-
-
-
-<h3><a name="sec25" id="sec25"></a>
-Procedural Only Where Neccesary</h3>
-
-<p class="first">Some operations like method invocation are inheretly stateful and so
-must use a procedural protocol. There is no benefit to be gained from
-using a functional protocol, and indeed an attempt would result in
-obtuse code that severely restricted the implementor. Do note that
-only a very small part of method invocation is stateful (the actual
-call), and most of it can be implemented functionally (e.g. computing
-the discriminating function).</p>
-
-
-
-<h2><a name="sec26" id="sec26"></a>
-Examples</h2>
-
-<h3><a name="sec27" id="sec27"></a>
-Object Inspector</h3>
-
-<p class="first">A primitive portable object inspector is presented here.</p>
-
 <pre class="src">
-(<span style="color: #00ffff;">defgeneric</span> <span style="color: #87cefa;">example-inspect</span> (instance)
-  (<span style="color: #b0c4de;">:documentation</span> <span style="color: #b3b3b3;">"Simple object inspector using CLOS MOP"</span>))
+(<span class="emacs-face-keyword">defgeneric</span> <span class="emacs-face-function-name">example-inspect</span> (instance)
+  (<span class="emacs-face-builtin">:documentation</span> <span class="emacs-face-doc">"Simple object inspector using CLOS MOP"</span>))
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">example-inspect</span> ((instance t))
-  (format t <span style="color: #b3b3b3;">"Simple Object~% Value: ~S~%"</span> instance))
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">example-inspect</span> ((instance t))
+  (format t <span class="emacs-face-string">"Simple Object~% Value: ~S~%"</span> instance))
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">example-inspect</span> ((instance standard-object))
-  (<span style="color: #00ffff;">let</span> ((class (class-of instance)))
-    (format t <span style="color: #b3b3b3;">"Class: ~S, Superclasses: ~S~%"</span>
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">example-inspect</span> ((instance standard-object))
+  (<span class="emacs-face-keyword">let</span> ((class (class-of instance)))
+    (format t <span class="emacs-face-string">"Class: ~S, Superclasses: ~S~%"</span>
             (class-name class)
             (mapcar #'class-name
                     (class-precedence-list class)))
-    (<span style="color: #00ffff;">let</span> ((slot-names (mapcar #'slot-definition-name
+    (<span class="emacs-face-keyword">let</span> ((slot-names (mapcar #'slot-definition-name
                               (class-slots class))))
-      (format t <span style="color: #b3b3b3;">"Slots: ~%~{ ~S~%~}"</span> slot-names)
+      (format t <span class="emacs-face-string">"Slots: ~%~{ ~S~%~}"</span> slot-names)
       (inspect-loop slot-names instance #'example-inspect))))
 
-(<span style="color: #00ffff;">defun</span> <span style="color: #87cefa;">inspect-loop</span> (slots instance inspector)
-  (format t <span style="color: #b3b3b3;">"Enter slot to inspect or :pop to go up one level: "</span>)
+(<span class="emacs-face-keyword">defun</span> <span class="emacs-face-function-name">inspect-loop</span> (slots instance inspector)
+  (format t <span class="emacs-face-string">"Enter slot to inspect or :pop to go up one level: "</span>)
   (finish-output)
-  (<span style="color: #00ffff;">let*</span> ((slot (read))
+  (<span class="emacs-face-keyword">let*</span> ((slot (read))
          (found-slot (member slot slots)))
-    (<span style="color: #00ffff;">cond</span> (found-slot
+    (<span class="emacs-face-keyword">cond</span> (found-slot
            (funcall inspector (slot-value instance slot))
            (funcall inspector instance))
-          ((eq slot <span style="color: #b0c4de;">:pop</span>) t)
+          ((eq slot <span class="emacs-face-builtin">:pop</span>) t)
           (t
-           (format t <span style="color: #b3b3b3;">"~S is invalid. Valid slot names: ~S~%"</span>
+           (format t <span class="emacs-face-string">"~S is invalid. Valid slot names: ~S~%"</span>
                    slot
                    slots)
            (inspect-loop slots instance inspector)))))
 </pre>
 
 
-<h3><a name="sec28" id="sec28"></a>
-Observer Design Pattern</h3>
+<h5>Example: Runtime Generated Classes and Methods</h5>
+
+
 
-<p class="first">A simple implementation of the observer pattern is under 100 lines,
+<h4><a name="sec16" id="sec16"></a>
+Intercessory</h4>
+
+<p class="first">Intercessory MOPs allow the user to customize language behavior by
+implementing methods which override certain aspects of the language
+behavior. This class of MOPs are what make MOPs especially
+powerful. No longer must a problem be restructured to fit the
+implementation language; the underlying language can be reshaped to
+fit the task at hand, and obfuscation of the intended structure of the
+application can be avoided.</p>
+
+<h5>Example: Lazily Allocated Slots</h5>
+
+
+<h5>Example: Observer Design Pattern</h5>
+
+<p>A simple implementation of the observer pattern is under 100 lines,
 and the user level code requires only a single line of code to make
 any existing class observable.</p>
 
 <p>In a language lacking a MOP, implementing the observer pattern
 requires modifying every accessor of a class to explicitly invoke any
-observers, and neccesitates the addition of a mixin class to the class
-heirarchy. The fact that an object can be observed is a meta property
+observers, and necessitates the addition of a mixin class to the class
+hierarchy. The fact that an object can be observed is a meta property
 of the class, and forcing it to be implemented at the application
-level dirties the inheritance heirarchy and adds uneccesary meta
+level dirties the inheritance hierarchy and adds unnecessary meta
 details to the program.</p>
 
 <pre class="src">
-<span style="color: #ff7f24;">;;; </span><span style="color: #ff7f24;">This metaclass adds a slot to instances which use it, and so the
-</span><span style="color: #ff7f24;">;;; </span><span style="color: #ff7f24;">system is defined in its own package to avoid name conflicts
-</span>(<span style="color: #00ffff;">defpackage</span> <span style="color: #98fb98;">:observer</span>
-  (<span style="color: #b0c4de;">:use</span> <span style="color: #b0c4de;">:cl</span> #+sbcl <span style="color: #b0c4de;">:sb-mop</span>)
-  (<span style="color: #b0c4de;">:export</span> observable register-observer unregister-observer))
+<span class="emacs-face-comment-delimiter">;;; </span><span class="emacs-face-comment">This metaclass adds a slot to instances which use it, and so the
+</span><span class="emacs-face-comment-delimiter">;;; </span><span class="emacs-face-comment">system is defined in its own package to avoid name conflicts
+</span>(<span class="emacs-face-keyword">defpackage</span> <span class="emacs-face-type">:observer</span>
+  (<span class="emacs-face-builtin">:use</span> <span class="emacs-face-builtin">:cl</span> <span class="emacs-face-builtin">:c2mop</span>)
+  (<span class="emacs-face-builtin">:export</span> observable register-observer unregister-observer))
 
-(<span style="color: #00ffff;">in-package</span> <span style="color: #b0c4de;">:observer</span>)
+(<span class="emacs-face-keyword">in-package</span> <span class="emacs-face-builtin">:observer</span>)
 
-<span style="color: #ff7f24;">;;; </span><span style="color: #ff7f24;">Metaclass
-</span>(<span style="color: #00ffff;">defclass</span> <span style="color: #98fb98;">observable</span> (standard-class)
+<span class="emacs-face-comment-delimiter">;;; </span><span class="emacs-face-comment">Metaclass
+</span>(<span class="emacs-face-keyword">defclass</span> <span class="emacs-face-type">observable</span> (standard-class)
   ()
-  (<span style="color: #b0c4de;">:documentation</span> <span style="color: #b3b3b3;">"Metaclass for observable objects"</span>))
+  (<span class="emacs-face-builtin">:documentation</span> <span class="emacs-face-doc">"Metaclass for observable objects"</span>))
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">compute-slots</span> ((class observable))
-  <span style="color: #b3b3b3;">"Add a slot for storing observers to observable instances"</span>
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">compute-slots</span> ((class observable))
+  <span class="emacs-face-doc">"Add a slot for storing observers to observable instances"</span>
   (cons (make-instance 'standard-effective-slot-definition
-                       <span style="color: #b0c4de;">:name</span> 'observers
-                       <span style="color: #b0c4de;">:initform</span> '(make-hash-table)
-                       <span style="color: #b0c4de;">:initfunction</span> #'(<span style="color: #00ffff;">lambda</span> () (make-hash-table)))
+                       <span class="emacs-face-builtin">:name</span> 'observers
+                       <span class="emacs-face-builtin">:initform</span> '(make-hash-table)
+                       <span class="emacs-face-builtin">:initfunction</span> #'(<span class="emacs-face-keyword">lambda</span> () (make-hash-table)))
         (call-next-method)))
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">validate-superclass</span> ((class observable)
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">validate-superclass</span> ((class observable)
                                 (super standard-class))
   t)
 
-(<span style="color: #00ffff;">defun</span> <span style="color: #87cefa;">register-observer</span> (instance slot-name key closure)
+(<span class="emacs-face-keyword">defun</span> <span class="emacs-face-function-name">register-observer</span> (instance slot-name key closure)
   (register-observer-with-class (class-of instance)
                                 instance
                                 slot-name
                                 key
                                 closure))
 
-(<span style="color: #00ffff;">defun</span> <span style="color: #87cefa;">unregister-observer</span> (instance slot-name key)
+(<span class="emacs-face-keyword">defun</span> <span class="emacs-face-function-name">unregister-observer</span> (instance slot-name key)
   (unregister-observer-with-class (class-of instance)
                                   instance
                                   slot-name
                                   key))
 
-(<span style="color: #00ffff;">defun</span> <span style="color: #87cefa;">get-observers</span> (instance slot-name)
+(<span class="emacs-face-keyword">defun</span> <span class="emacs-face-function-name">get-observers</span> (instance slot-name)
   (get-observers-with-class (class-of instance)
                             instance
                             slot-name))
 
-(<span style="color: #00ffff;">defun</span> <span style="color: #87cefa;">add-observer-table</span> (instance slot-name)
+(<span class="emacs-face-keyword">defun</span> <span class="emacs-face-function-name">add-observer-table</span> (instance slot-name)
   (setf (gethash slot-name (slot-value instance
                                        'observers))
         (make-hash-table)))
 
-(<span style="color: #00ffff;">defgeneric</span> <span style="color: #87cefa;">register-observer-with-class</span> (class instance slot-name key closure))
-(<span style="color: #00ffff;">defgeneric</span> <span style="color: #87cefa;">unregister-observer-with-class</span> (class
+(<span class="emacs-face-keyword">defgeneric</span> <span class="emacs-face-function-name">register-observer-with-class</span> (class instance slot-name key closure))
+(<span class="emacs-face-keyword">defgeneric</span> <span class="emacs-face-function-name">unregister-observer-with-class</span> (class
                                             instance
                                             slot-name
                                             key))
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">register-observer-with-class</span> ((class observable)
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">register-observer-with-class</span> ((class observable)
                                          instance
                                          slot-name
                                          key
@@ -650,34 +538,34 @@ details to the program.</p>
   (setf (gethash key
                  (or (gethash slot-name
                               (slot-value instance 'observers))
-                     <span style="color: #ff7f24;">;; </span><span style="color: #ff7f24;">Lazily add observer hash tables
+                     <span class="emacs-face-comment-delimiter">;; </span><span class="emacs-face-comment">Lazily add observer hash tables
 </span>                     (add-observer-table instance slot-name)))
         closure))
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">unregister-observer-with-class</span> ((class observable)
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">unregister-observer-with-class</span> ((class observable)
                                            instance
                                            slot-name
                                            key)
   (remhash key (gethash slot-name
                         (slot-value instance 'observers))))
 
-(<span style="color: #00ffff;">defmethod</span> <span style="color: #87cefa;">get-observers-with-class</span> ((class observable)
+(<span class="emacs-face-keyword">defmethod</span> <span class="emacs-face-function-name">get-observers-with-class</span> ((class observable)
                                      instance
                                      slot-name)
   (gethash slot-name (slot-value instance 'observers)))
 
-(<span style="color: #00ffff;">defmethod</span> (<span style="color: #87cefa;">setf slot-value-using-class)</span> <span style="color: #b0c4de;">:before</span> (new-value
+(<span class="emacs-face-keyword">defmethod</span> (<span class="emacs-face-function-name">setf slot-value-using-class</span>) <span class="emacs-face-builtin">:before</span> (new-value
                                                   (class observable)
                                                   instance
                                                   slot)
-  (<span style="color: #00ffff;">let</span> ((slot-name (slot-definition-name slot)))
-    (<span style="color: #00ffff;">if</span> (not (eq 'observers slot-name))
-        (<span style="color: #00ffff;">let</span> ((observers
+  (<span class="emacs-face-keyword">let</span> ((slot-name (slot-definition-name slot)))
+    (<span class="emacs-face-keyword">if</span> (not (eq 'observers slot-name))
+        (<span class="emacs-face-keyword">let</span> ((observers
                (get-observers instance (slot-definition-name slot))))
-          (<span style="color: #00ffff;">if</span> observers
-              (maphash #'(<span style="color: #00ffff;">lambda</span> (key observer)
+          (<span class="emacs-face-keyword">if</span> observers
+              (maphash #'(<span class="emacs-face-keyword">lambda</span> (key observer)
                            (funcall observer
-                                    (<span style="color: #00ffff;">if</span> (slot-boundp instance slot-name)
+                                    (<span class="emacs-face-keyword">if</span> (slot-boundp instance slot-name)
                                         (slot-value instance slot-name)
                                       nil)
                                     new-value))
@@ -685,13 +573,111 @@ details to the program.</p>
 </pre>
 
 
-<h3><a name="sec29" id="sec29"></a>
+
+
+
+<h3><a name="sec17" id="sec17"></a>
+Violation of Encapsulation?</h3>
+
+<p class="first">A MOP may seem like a violation of encapsulation by revealing some
+implementation details, but in reality a well designed protocol does
+not reveal anything which was not already exposed. Implementation
+decisions affect users, and some of these details do leak through to
+higher levels (e.g. the memory layout of slots). Implicit in the
+protocol specification are these implementation details, and the MOP
+merely makes this limited subset available for customization.</p>
+
+<p>A MOP makes it possible to customize certain implementation decisions
+that do not <strong>radically</strong> alter the behavior of the base language. The
+conceptual vocabulary of the system retains its meaning, and so code
+written in one dialect can interact with code written in another
+without knowing that they speak different ones.</p>
+
+
+
+<h2><a name="sec18" id="sec18"></a>
+MOP Design Principles</h2>
+
+<h3><a name="sec19" id="sec19"></a>
+Layered Protocol</h3>
+
+<p class="first">A layered protocol design is good for both meta and normal object
+protocols, and enables a combinatorial explosion of customizations to
+the protocol.</p>
+
+<h4><a name="sec20" id="sec20"></a>
+Top Level <strong>Must</strong> Call Lower Level Methods</h4>
+
+<p class="first">The top level methods of a layered protocol are required to call
+certain lower level methods to perform some tasks. This both makes it
+easier to customize the top level methods (which perform very broad
+tasks) by providing some pieces of implementation for the programmer,
+and enables more customization by opening up the replacement of lower
+level functions as a way to alter a small detail of the high level
+behavior.</p>
+
+
+<h4><a name="sec21" id="sec21"></a>
+Lower Level Methods are Easier to Customize</h4>
+
+<p class="first">The lower level methods of a MOP are limited in scope and can be
+implemented easily. Often the desired changes to language behavior are
+minor, and having methods that perform simple tasks which are often
+customized reduces the effort required to extend the system.</p>
+
+
+
+<h3><a name="sec22" id="sec22"></a>
+Functional Where Possible</h3>
+
+<p class="first">Functional protocols are preferred for MOPs (and object protocols in
+general). Functional protocols open up several optimizations for the
+implementation without burdening the user of the protocol.</p>
+
+<h4><a name="sec23" id="sec23"></a>
+Memoization</h4>
+
+<p class="first">Memoization is the process of saving the results of a function call
+for future use. This avoids expensive recomputation of values which
+have not changed (recall that a true function will always return the
+same result when given the same arguments).</p>
+
+<p>A functional MOP can be optimized easily by exploiting this property
+to memoize the return values of calls to expensive operations. A MOP
+must be be very fast to avoid making programs unusably slow, and
+memoization is able to give an appreciable speedup in many cases
+without a significant burden on memory usage.</p>
+
+
+<h4><a name="sec24" id="sec24"></a>
+Constant Shared Return Values</h4>
+
+<p class="first">Disallowing modification of values returned by protocol methods allows
+the implementation to return large data structures by reference to
+avoid expensive copying without having to do expensive data integrity
+checks or copying.</p>
+
+
+
+<h3><a name="sec25" id="sec25"></a>
+Procedural Only Where Necessary</h3>
+
+<p class="first">Some operations like method invocation are inherently stateful and so
+must use a procedural protocol. There is no benefit to be gained from
+using a functional protocol, and indeed an attempt would result in
+obtuse code that severely restricted the implementation. Do note that
+only a very small part of method invocation is stateful (the actual
+call), and most of it can be implemented functionally (e.g. computing
+the discriminating function).</p>
+
+
+<h3><a name="sec26" id="sec26"></a>
 Real World</h3>
 
-<h4><a name="sec30" id="sec30"></a>
+<h4><a name="sec27" id="sec27"></a>
 <a href="http://common-lisp.net/project/ucw/">UCW</a> and <a href="http://common-lisp.net/project/bese/arnesi.html">Arnesi</a></h4>
 
-<p class="first">Arnesi uses the CLOS MOP to implement methods which are transparantly
+<p class="first">Arnesi uses the CLOS MOP to implement methods which are transparently
 rewritten into continuation passing style. This allows their execution
 to be suspended at certain points and resumed later. UCW builds on top
 of this to support a web framework where the statelessness of http is
@@ -700,7 +686,7 @@ current continuation, and resumes it upon submission. The user level
 code is completely unaware of this.</p>
 
 
-<h4><a name="sec31" id="sec31"></a>
+<h4><a name="sec28" id="sec28"></a>
 <a href="http://clsql.b9.com">CLSQL</a></h4>
 
 <p class="first">CLSQL uses the reflective part of the CLOS MOP to map Common Lisp data
@@ -709,23 +695,23 @@ allocation to map slots onto database columns or sql expressions (for
 implementing relational slots).</p>
 
 
-<h4><a name="sec32" id="sec32"></a>
+<h4><a name="sec29" id="sec29"></a>
 <a href="http://common-lisp.net/project/elephant/">Elephant</a></h4>
 
-<p class="first">Elephant uses the CLOS MOP to transparantly store any class to disk
-and handle paging between the disk store and memory efficiently and
-with no user intervention.</p>
+<p class="first">Elephant uses the CLOS MOP to transparently store any class to disk
+and handle paging between the disk store and memory efficiently
+without user intervention.</p>
 
 
 
 
-<h2><a name="sec33" id="sec33"></a>
-Sources &amp;amp; Further Reading</h2>
+<h2><a name="sec30" id="sec30"></a>
+Sources and Further Reading</h2>
 
-<h3><a name="sec34" id="sec34"></a>
+<h3><a name="sec31" id="sec31"></a>
 Sources</h3>
 
-<h4><a name="sec35" id="sec35"></a>
+<h4><a name="sec32" id="sec32"></a>
 The Art of the Metaobject Protocol</h4>
 
 <h5>Kiczales, Gregor et al. MIT Press 1991</h5>
@@ -736,20 +722,20 @@ useful.</p>
 
 
 
-<h4><a name="sec36" id="sec36"></a>
+<h4><a name="sec33" id="sec33"></a>
 <a href="http://www.lisp.org/mop/contents.html">CLOS MOP Specification</a></h4>
 
 <p class="first">Specification of the MOP for CLOS defined in <em>The Art of the Metaobject Protocol</em>.</p>
 
 
-<h4><a name="sec37" id="sec37"></a>
+<h4><a name="sec34" id="sec34"></a>
 <a href="http://citeseer.ist.psu.edu/399658.html">Metaobject Protocols: Why We Want Them and What Else They Can Do</a></h4>
 
 <p class="first">A short overview of MOP design principles followed by three example
 metaobject protocols for Scheme.</p>
 
 
-<h4><a name="sec38" id="sec38"></a>
+<h4><a name="sec35" id="sec35"></a>
 <a href="http://www2.parc.com/csl/groups/sda/projects/oi/towards-talk/transcript.html">Why Are Black Boxes so Hard to Reuse?</a></h4>
 
 <p class="first">Transcription of a talk on the benefits of open implementations of
@@ -760,17 +746,17 @@ metaobject protocols as a solution to most of the problems.</p>
 
 
 
-<h3><a name="sec39" id="sec39"></a>
+<h3><a name="sec36" id="sec36"></a>
 Further Reading</h3>
 
-<h4><a name="sec40" id="sec40"></a>
+<h4><a name="sec37" id="sec37"></a>
 <a href="http://citeseer.ist.psu.edu/chiba95metaobject.html">A Metaobject Protocol for C++</a></h4>
 
 <p class="first">Example of a purely compile time MOP. It implements the functionality
 of a code walker and something similar to the Lisp macro system.</p>
 
 
-<h4><a name="sec41" id="sec41"></a>
+<h4><a name="sec38" id="sec38"></a>
 <a href="http://www.parc.com/csl/groups/sda/publications/papers/Kiczales-TUT95/for-web.pdf">Open Implementations and Metaobject Protocols</a></h4>
 
 <p class="first">It is a bit long, but it seems to follow a similar structure to AMOP
@@ -779,6 +765,18 @@ notes, and so the 331 pages might not actually take that long to read.</p>
 
 
 
+<h3><a name="sec39" id="sec39"></a>
+Software</h3>
+
+<h4><a name="sec40" id="sec40"></a>
+<a href="http://common-lisp.net/project/closer/closer-mop.html">Closer to MOP</a></h4>
+
+<p class="first">Compatibility layer that attempts to present the <em>Art of the Metaobject
+Protocol</em> MOP specification properly in as many Common Lisp
+implementation as possible.</p>
+
+
+
 
   <!-- Page published by Emacs Muse ends here -->
 
@@ -806,9 +804,9 @@ notes, and so the 331 pages might not actually take that long to read.</p>
     </a>
   </p>
 
-<p class="cke-footer">Mike: I WAS NOT MICROWAVED.
+<p class="cke-footer">No, there's nothing here about X, so be quiet.
 </p>
 <p class="cke-timestamp">Last Modified:
-    March 13, 2008</p>
+    January 21, 2013</p>
   </body>
 </html>
\ No newline at end of file